import 'dart:convert';
import 'package:dio/dio.dart';
import 'package:flutter_study_2025/aes/aes_utils.dart';

/// 网络请求管理类（单例）
class NetworkManager {
  // 单例实例
  static final NetworkManager _instance = NetworkManager._internal();

  // Dio实例
  late Dio _dio;

  // 基础URL
  final String _baseUrl = "https://api.misstory789.online/api/asf/";

  // 是否开启日志打印
  final bool _enableLog = true;

  // 工厂构造函数
  factory NetworkManager() => _instance;

  // 私有构造函数
  NetworkManager._internal() {
    // 初始化Dio
    _dio = Dio(
      BaseOptions(
        baseUrl: _baseUrl,
        connectTimeout: const Duration(seconds: 10),
        receiveTimeout: const Duration(seconds: 10),
        sendTimeout: const Duration(seconds: 10),
        contentType: "application/json",
      ),
    );

    // 设置默认请求头
    _setDefaultHeaders();

    // 添加拦截器
    _addInterceptors();
  }

  // 设置默认请求头
  void _setDefaultHeaders() {
    _dio.options.headers.addAll({
      'Content-Type': 'application/json-patch+json',
      'Accept': 'application/json',
      // 可添加其他默认头信息，如App版本、设备信息等
      // 'App-Version': '1.0.0',
      // 'Device-Type': 'mobile',
    });
  }

  // 添加拦截器
  void _addInterceptors() {
    _dio.interceptors.add(
      InterceptorsWrapper(
        onRequest: (options, handler) {
          // 请求拦截处理
          if (_enableLog) {
            print("请求URL: ${options.uri}");
            print("请求参数: ${options.data ?? options.queryParameters}");
          }
          handler.next(options);
        },
        onResponse: (response, handler) {
          // 响应拦截处理
          if (_enableLog) {
            print("响应数据: ${response.data}");
          }
          handler.next(response);
        },
        onError: (DioException e, handler) {
          // 错误拦截处理
          if (_enableLog) {
            print("请求错误: ${e.message}");
            print("错误代码: ${e.response?.statusCode}");
          }
          handler.next(e);
        },
      ),
    );

    // 日志拦截器
    if (_enableLog) {
      _dio.interceptors.add(
        LogInterceptor(
          requestBody: true,
          responseBody: true,
          requestHeader: true,
          responseHeader: true,
        ),
      );
    }
  }

  // GET请求
  Future<T> get<T>(
    String path, {
    Map<String, dynamic>? queryParameters,
    bool needEncrypt = false, // 是否需要加密
    Options? options,
    CancelToken? cancelToken,
  }) async {
    try {
      // 如果需要加密，处理参数
      if (needEncrypt &&
          queryParameters != null &&
          queryParameters.isNotEmpty) {
        final paramsJson = json.encode(queryParameters);
        queryParameters = {"data": AESUtil.encryptECB(paramsJson)};
      }

      final response = await _dio.get(
        path,
        queryParameters: queryParameters,
        options: options,
        cancelToken: cancelToken,
      );

      // 处理加密响应
      if (needEncrypt && response.data is Map) {
        final dataMap = response.data as Map;
        if (dataMap.containsKey("data") && dataMap["data"] is String) {
          final decryptedData = AESUtil.encryptECB(dataMap["data"] as String);
          return json.decode(decryptedData) as T;
        }
      }

      return response.data as T;
    } on DioException catch (e) {
      print("GET请求错误: ${e.message}");
      rethrow;
    } catch (e) {
      print("GET请求异常: $e");
      rethrow;
    }
  }

  // POST请求
  Future<T> post<T>(
    String path, {
    dynamic data,
    bool needEncrypt = false, // 是否需要加密
    Map<String, dynamic>? queryParameters,
    Options? options,
    CancelToken? cancelToken,
  }) async {
    try {
      // 如果需要加密，处理请求数据
      if (needEncrypt && data != null) {
        final dataJson = json.encode(data);
        data = {"data": AESUtil.encryptECB(dataJson)};
      }

      final response = await _dio.post(
        path,
        data: data,
        queryParameters: queryParameters,
        options: options,
        cancelToken: cancelToken,
      );

      // 处理加密响应
      if (needEncrypt && response.data is Map) {
        final dataMap = response.data as Map;
        if (dataMap.containsKey("data") && dataMap["data"] is String) {
          final decryptedData = AESUtil.encryptECB(dataMap["data"] as String);
          return json.decode(decryptedData) as T;
        }
      }

      return response.data as T;
    } on DioException catch (e) {
      print("POST请求错误: ${e.message}");
      rethrow;
    } catch (e) {
      print("POST请求异常: $e");
      rethrow;
    }
  }

  // 取消所有请求
  void cancelAllRequests() {
    _dio.close(force: true); // 强制关闭所有请求连接
  }
}
